#!/bin/bash
# This script is released under the GNU General Public License 3.0
# Check the COPYING file included with this distribution

DESTDIR="/mnt/gentoo"
EDITOR=

# clock
HARDWARECLOCK=
TIMEZONE=

# install stages
S_CLOCK=0		# clock and timezone
S_PART=0		# partitioning
S_MKFS=0		# formatting
S_MKFSAUTO=0	# auto fs part/formatting TODO: kill this
S_CONFIG=0		# configuration editing
S_GRUB=0		# TODO: kill this - if using grub
S_BOOT=""		# bootloader installed (set to loader name instead of 1)
S_FDE=0		 	# Full disk encryption, need key in /boot

# main menu selection tracker
CURRENT_SELECTION=""

# getuuid()
# converts /dev/[hs]d?[0-9] devices to UUIDs
#
# parameters: device file
# outputs:	UUID on success
#			 nothing on failure
# returns:	nothing
getuuid()
{
	if [ "${1%%/[hs]d?[0-9]}" != "${1}" ]; then
		echo "$(blkid -s UUID -o value ${1})"
	fi
}

# douefigrub()
# writes kernel to UEFI as new boot option
# parameters:
#	 kernelpath: path to kernel, relative to partition root
#	 initrdpath: path to initrd
#	 bootparams: other boot params for kernel
# returns: 1 on failure
douefigrub() {
	# check if grub2 is installed
	grub2-mkimage -? 2>/dev/null 1>&2
	if [ $? -ne 0 ]; then
		show_dialog --msgbox "Error: Couldn't find grub2-mkimage. Is GRUB-2 installed?" 0 0
		return 1
	fi
	local kernelpath="${1}"
	local initrdpath="${2}"
	local bootparams="${3}"
	# uefipart: uefi partition, ex. /dev/sda1
	show_dialog --menu "Select the partition to use as UEFI boot partition" 21 50 13 NONE - ${PARTS} 2>"${ANSWER}" || return 1
	local uefipart=$(get_answer)
	PARTS="$(echo ${PARTS} | sed -e "s#${uefipart}\ _##g")"
	[ "${uefipart}" = "NONE" ] && return 1
	# grubpart: grub partition, ex. (hd0,2)
	show_dialog --inputbox "Verify your GRUB device path" 8 65 "(hd0,2)" 2>"${ANSWER}" || return 1
	local grubpart=$(get_answer)
	# uefimount: uefi partition mount point, ex. /boot
	local uefimount="$(mount | grep "^${uefipart} " | cut -d' ' -f 3)"
	# mount if not mounted
	if [ "${uefimount}" = "" ]; then
		mkdir -p /tmp/efibootpart || return 1
		mount "${uefipart}" /tmp/efibootpart || return 1
		uefimount=/tmp/efibootpart
	fi
	# safety check for /EFI/BOOT/BOOTX64.EFI (case insensitive for fat)
	local findefi="$(find "${uefimount}" -iwholename "${uefimount}/efi/boot/bootx64.efi")"
	if [ "${findefi}" != "" ]; then
		show_dialog --msgbox "Error: ${findefi} exists, refusing to overwrite!" 0 0
		return 1
	fi
	# safety check for /boot/grub2 (case insensitive for fat)
	local findgrub2="$(find "${uefimount}" -iwholename "${uefimount}/boot/grub2")"
	if [ "${findgrub2}" != "" ]; then
		show_dialog --msgbox "Error: ${findgrub2} exists, refusing to overwrite!" 0 0
		return 1
	fi
	# create grub image
	mkdir -p "${uefimount}/EFI/BOOT" || return 1
	grub2-mkimage -p /boot/grub2 -o "${uefimount}/EFI/BOOT/BOOTX64.EFI" -O x86_64-efi part_msdos part_gpt fat normal \
		|| return 1
	# copy grub modules
	mkdir -p "${uefimount}/boot/grub2" || return 1
	cp -ar /usr/lib/grub/x86_64-efi "${uefimount}/boot/grub2/" \
		|| return 1
	# create a crude grug.cfg
	mkdir -p "${uefimount}/boot/grub2" || return 1
	cat >> "${uefimount}/boot/grub2/grub.cfg" <<EOF
timeout=5
menuentry 'Pentoo' {
	insmod efi_gop
	insmod efi_uga
	insmod part_msdos
	insmod part_gpt
	root=${grubpart}
	linux ${kernelpath} ${bootparams}
	initrd ${initrdpath}
}
EOF
	show_dialog --msgbox "UEFI boot image successfully installed. You can now review the GRUB-2 config file." 0 0
	[ "${EDITOR}" ] || seteditor
	${EDITOR} "${uefimount}/boot/grub2/grub.cfg"
	show_dialog --msgbox "Success: UEFI booting by GRUB-2 installed!" 0 0
}

# dobootloader()
# installs boot loader
# parameters:
#	 bootmode:
#		 - uefigrub: installs GRUB2 UEFI-image plus menu
#		 - uefi: boot kernel direclty by UEFI
# returns: 1 on failure
#
dobootloader() {
	local bootmode="${1}"
	local _kernver=
	_kernver=$(getkernelversion)
	local kernelpath="/boot/kernel-genkernel${_kernver}"
	local initrdpath="/boot/initramfs-genkernel${_kernver}"
	local bootparams="root=/dev/ram0 real_root=${PART_ROOT}"
	# select UEFI boot partition
	PARTS=$(findpartitions _)
	# compose boot parameters
	# parse kernel cmdline (only video mode for now)
	for _var in $(cat /proc/cmdline); do
		case ${_var} in
			video=*)
				eval $(echo ${_var}) ;;
		esac
	done
	bootparams+=" video=${video} console=tty0 usbcore.autosuspend=1 net.ifnames=0 ro"
	case "${bootmode}" in
		uefigrub)
			douefigrub "${kernelpath}" "${initrdpath}" "${bootparams}" \
				|| return 1
			;;
		uefi)
			douefi "${kernelpath}" "${initrdpath}" "${bootparams}" \
			|| return 1
			;;
	esac
}
